/*************************************************************************
This class provides the functionality to parse a input file that is in XML
format.  The tinyXML (which can be found in sourceforge.net) is used to parse
the input file.  In a typical input file, users should give required information.
The information includes the purpose, probabiility of crossover, probabilitiy
of mutation, number of generation, model configuration, model parameters,
adouble average rainfall ,observed runoff, watershed area and time interval.
There are three kind of purposes.  They are simulation, calibration and both the simulation and 
calibration.
In all purpose of using the model, water area and time interval are all required.
In simulation, the required data is model configuration
Author:Chun-Ming Wang (04/12/2007) (dd/mm/yyyy)
*************************************************************************/
#pragma once
#ifndef _InputData
#define _InputData
#include <vector>
#include <string>
#include<boost/tokenizer.hpp>
#include <tinyxml.h>
#include "..\NCUCModel\Misc.h"
using namespace std;
class InputData
{
public:
	typedef vector<string> StringContainer;
	typedef vector<string>::iterator SCIter; // iterator of StringContainer
	typedef vector<double> doubleContainer;
	typedef vector<double>::iterator RCIter;
	// constructors
	InputData();
	InputData(const string& filename);
	// destructor
	~InputData();
	// copy constructor
	//InputData(const InputData& rhs);
	// assignment operator
	//InputData& operator=(const InputData& rhs);
	// access function
	bool LoadFile(const string& filename);
	// necessary data
	bool area(double& a) const;
	bool TimeInterval( unsigned int& ti ) const;
	// model configuration
	bool ModelConfiguration(string& con) const;
	bool ModelParameters(doubleContainer& mp) const;
	// genetic algorithms parameters
	bool nGeneration(unsigned int& n) const;
	bool nPopulation(unsigned int& n) const;
	bool pCrossOver(double& p) const;
	bool pMutation(double& p) const;
	// rainfall records
	bool ObservedRainfall(doubleContainer& or) const;
	bool OptionalRainfall(doubleContainer& or) const;
	// runoff records
	bool ObservedRunoff(doubleContainer& or) const;
	bool OptionalRunoff(doubleContainer& or) const;
	// objective function
	bool ObjectiveFunction(string& of) const;
	//
	InputData* clone() const;
protected:
	const TiXmlElement* query(const string& name) const; // query the label specified by the name passed into the function
	bool Text(const TiXmlElement* const pElm, string& content) const;
	bool retrieve(const string& label, unsigned int& data) const;
	bool retrieve(const string& label, double& data) const;
	bool retrieve(const string& label, string& data) const;
	bool retrieve(const string& label, doubleContainer& data) const;
	vector<double> token(const string& input) const;
	vector<string> element(const string& input) const;
private:
	// Here a function pointer is required.
	TiXmlDocument _doc; // the input file
public:
	// get Sill Length
	bool SillLength(double& n) const;
	// get Sill lower bound
	bool SillLowerBound(double& lower) const;
	// get Sill upper bound
	bool SillUpperBound(double& upper) const;
	// get Sill upper bound
};
#endif